package com.jwww.support.mybatis;

import com.jwww.support.mybatis.beans.MapResultItem;
import org.apache.commons.io.FileUtils;
import org.apache.commons.io.IOUtils;

import java.io.File;
import java.io.FileFilter;
import java.io.IOException;
import java.io.InputStream;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

/**
 * mybatis generator生成mapper文件格式化工具<br>
 * 生成对应接口@see IGenericEntityDao 的方法
 * @author jwww
 * @date 2015年6月4日下午5:19:32
 * @description <br>
 * Copyright (c) 2015, vakinge@gmail.com.
 */
public class MybatisMapperFormater {
	
	static Map<String, String> replacer = new HashMap<String, String>();
	


	public static void main(String[] args) throws Exception {
		
		String mapperDir = "D:/workspace/mybatis-generator/src/com/jwww/demo/dao";//待格式化的mapping文件夹路径
		String outputDir = "D:/dao/demo";//格式化完成文件夹路径
		
		doFormat(mapperDir, outputDir);
	}



	public static void doFormat(String mapperDir, String outputDir)
			throws IOException {
		File dir = new File(mapperDir);
		if(dir.exists() == false){
			System.err.println("输入文件夹不存在");
			return;
		}
		
		File[] mapperFiles = dir.listFiles(new FileFilter() {
			@Override
			public boolean accept(File fname) {
				return fname.getName().endsWith(".xml");
			}
		});
		
		File output = new File(outputDir);
		if(output.exists() == false)output.mkdirs();
		for (File file : mapperFiles) {
			formatMappingFile(file,output);
		}
	}



	private static void formatMappingFile(File file,File outputDir) throws IOException {
		List<String> lines = FileUtils.readLines(file);
		
		List<MapResultItem> columnItems = MybatisMapperResultConverter.parseColumnsFromResultMapLine(lines);
		Map<String, MapResultItem> columnItemsMap = new HashMap<String, MapResultItem>();
		String idPropName = null;
		for (MapResultItem mapResultItem : columnItems) {
			if(mapResultItem.isPrimaryKey())idPropName = mapResultItem.getColumnName();
			columnItemsMap.put(mapResultItem.getPropertyName(), mapResultItem);
		}
		
		List<String> formatLines = new ArrayList<String>();
		
		String tableName = null,idColumnName = "";
		boolean ingore = false;
		boolean isUpdate = false;
		for (String line : lines) {
			if(line == null || line.trim().length() == 0)continue;
			if(line.contains("</mapper>"))continue;
			//<id column=
			if(line.matches(".*<id\\s+column=.*")){
				idColumnName = line.split("column")[1].trim().split("\\s+")[0].replaceAll("[\\s+\"=]", "");
			}
			
			if(tableName == null && line.matches(".*\\s+from\\s+.*")){
				tableName = line.split("from")[1].trim().split("\\s+")[0];
			}
			if(!ingore)ingore = line.contains("\"insert\"") || line.contains("\"updateByPrimaryKey\"");
			if(ingore){
				if(line.contains("</insert>") || line.contains("</update>")){
					ingore = false;
				}
				continue;
			}
			
			
			
			if(line.contains("selectByPrimaryKey")){
				line = line.replace("selectByPrimaryKey", "getById");
			}else if(line.contains("deleteByPrimaryKey")){
				line = line.replace("deleteByPrimaryKey", "deleteById");
			}else if(line.contains("insertSelective")){
				line = line.replace("insertSelective\"", "insert\" useGeneratedKeys=\"true\" keyProperty=\""+idPropName+"\"");
			}else if(line.contains("updateByPrimaryKeySelective")){
				isUpdate = true;
				line = line.replaceAll("<update id=\"updateByPrimaryKeySelective\".*>", "<update id=\"update\" parameterType=\"map\" >");
			}else if(line.contains("</update>")){
				if(isUpdate)isUpdate = false;
			}else if(line.matches(".*<if\\s+test=.*")){
				String propName = line.split("test=\"")[1].replaceAll("\\s*\\!=.*", "");
				if(isUpdate && columnItemsMap.containsKey(propName) && columnItemsMap.get(propName).isNumberType()){
					line = line.split("null")[0] + "null and "+propName+" gt 0\" >";
				}
			}
			
			formatLines.add(line);
		}
		
		InputStream stream = Thread.currentThread().getContextClassLoader().getResourceAsStream("extramapper.xml");
		lines = IOUtils.readLines(stream,"UTF-8");
		for (String line : lines) {
			formatLines.add(line.replaceAll("\\[table\\]", tableName).replaceAll("\\[id\\]", idColumnName));
		}
		
		formatLines.add("</mapper>");
		
		File outputFile = new File(outputDir,file.getName());
		FileUtils.writeLines(outputFile, formatLines);
		
		System.out.println("转换["+file.getName()+"]完成,输出文件："+outputFile.getAbsolutePath());
	}

}
